﻿<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE beans PUBLIC "-//SPRING//DTD BEAN//EN"
        "http://www.springframework.org/dtd/spring-beans.dtd">

<beans>
    <!-- ~~~~~~~~~~~~~~~~~~ "BEFORE INVOCATION" AUTHORIZATION DEFINITIONS ~~~~~~~~~~~~~~~~ -->

    <!-- 定义ACL MARK的静态字段，方便在xml配置文件中写Mark -->
    <bean id="org.acegisecurity.acl.basic.SimpleAclEntry.ADMINISTRATION" class="org.springframework.beans.factory.config.FieldRetrievingFactoryBean">
        <property name="staticField">
            <value>org.acegisecurity.acl.basic.SimpleAclEntry.ADMINISTRATION</value>
        </property>
    </bean>
    <bean id="org.acegisecurity.acl.basic.SimpleAclEntry.READ" class="org.springframework.beans.factory.config.FieldRetrievingFactoryBean">
        <property name="staticField">
            <value>org.acegisecurity.acl.basic.SimpleAclEntry.READ</value>
        </property>
    </bean>
    <bean id="org.acegisecurity.acl.basic.SimpleAclEntry.DELETE" class="org.springframework.beans.factory.config.FieldRetrievingFactoryBean">
        <property name="staticField">
            <value>org.acegisecurity.acl.basic.SimpleAclEntry.DELETE</value>
        </property>
    </bean>

    <!-- An access decision voter that reads ACL_Bean_READ configuration settings -->
    <bean id="aclBeanReadVoter" class="org.acegisecurity.vote.BasicAclEntryVoter">
        <property name="processConfigAttribute">
            <value>ACL_READ</value>
        </property>
        <property name="processDomainObjectClass">
            <value>org.springside.modules.security.acl.domain.AclDomainAware</value>
        </property>
        <property name="aclManager">
            <ref local="aclManager"/>
        </property>
        <property name="requirePermission">
            <list>
                <ref local="org.acegisecurity.acl.basic.SimpleAclEntry.ADMINISTRATION"/>
                <ref local="org.acegisecurity.acl.basic.SimpleAclEntry.READ"/>
            </list>
        </property>
    </bean>

    <!-- An access decision voter that reads ACL_Bean_DELETE configuration settings -->
    <bean id="aclBeanDeleteVoter" class="org.springside.modules.security.acl.voter.IdParameterAclEntryVoter">
        <property name="processConfigAttribute">
            <value>ACL_DELETE</value>
        </property>
        <property name="aclManager">
            <ref local="aclManager"/>
        </property>
        <property name="requirePermission">
            <list>
                <ref local="org.acegisecurity.acl.basic.SimpleAclEntry.ADMINISTRATION"/>
                <ref local="org.acegisecurity.acl.basic.SimpleAclEntry.DELETE"/>
            </list>
        </property>
    </bean>

    <!-- An access decision voter that reads ACL_Bean_ADMIN configuration settings -->
    <bean id="aclBeanAdminVoter" class="org.acegisecurity.vote.BasicAclEntryVoter">
        <property name="processConfigAttribute">
            <value>ACL_ADMIN</value>
        </property>
        <property name="processDomainObjectClass">
            <value>org.springside.modules.security.acl.domain.AclDomainAware</value>
        </property>
        <property name="aclManager">
            <ref local="aclManager"/>
        </property>
        <property name="requirePermission">
            <list>
                <ref local="org.acegisecurity.acl.basic.SimpleAclEntry.ADMINISTRATION"/>
            </list>
        </property>
    </bean>

    <!-- An access decision manager used by the business objects -->
    <bean id="businessAccessDecisionManager" class="org.acegisecurity.vote.AffirmativeBased">
        <property name="allowIfAllAbstainDecisions">
            <value>false</value>
        </property>
        <property name="decisionVoters">
            <list>
                <ref bean="roleVoter"/>
                <ref local="aclBeanReadVoter"/>
                <ref local="aclBeanDeleteVoter"/>
                <ref local="aclBeanAdminVoter"/>
            </list>
        </property>
    </bean>

    <!-- ========= ACCESS CONTROL LIST LOOKUP MANAGER DEFINITIONS ========= -->

    <bean id="aclManager" class="org.acegisecurity.acl.AclProviderManager">
        <property name="providers">
            <list>
                <ref local="basicAclProvider"/>
            </list>
        </property>
    </bean>

    <bean id="basicAclProvider" class="org.acegisecurity.acl.basic.BasicAclProvider">
        <property name="basicAclDao">
            <ref local="basicAclExtendedDao"/>
        </property>
    </bean>

    <bean id="basicAclExtendedDao" class="org.acegisecurity.acl.basic.jdbc.JdbcExtendedDaoImpl">
        <property name="dataSource">
            <ref bean="dataSource"/>
        </property>
    </bean>

    <!-- ============== "AFTER INTERCEPTION" AUTHORIZATION DEFINITIONS =========== -->

    <bean id="afterInvocationManager" class="org.acegisecurity.afterinvocation.AfterInvocationProviderManager">
        <property name="providers">
            <list>
                <ref local="afterAclRead"/>
                <ref local="afterAclDelete"/>
                <ref local="afterAclCreat"/>
                <ref local="afterAclCollectionRead"/>
            </list>
        </property>
    </bean>

    <!-- Processes AFTER_ACL_COLLECTION_READ configuration settings -->
    <bean id="afterAclCollectionRead" class="org.acegisecurity.afterinvocation.BasicAclEntryAfterInvocationCollectionFilteringProvider">
        <property name="aclManager">
            <ref local="aclManager"/>
        </property>
        <property name="requirePermission">
            <list>
                <ref local="org.acegisecurity.acl.basic.SimpleAclEntry.ADMINISTRATION"/>
                <ref local="org.acegisecurity.acl.basic.SimpleAclEntry.READ"/>
            </list>
        </property>
    </bean>

    <!-- Processes AFTER_ACL_READ configuration settings -->
    <bean id="afterAclRead" class="org.acegisecurity.afterinvocation.BasicAclEntryAfterInvocationProvider">
        <property name="aclManager">
            <ref local="aclManager"/>
        </property>
        <property name="requirePermission">
            <list>
                <ref local="org.acegisecurity.acl.basic.SimpleAclEntry.ADMINISTRATION"/>
                <ref local="org.acegisecurity.acl.basic.SimpleAclEntry.READ"/>
            </list>
        </property>
    </bean>

    <!-- Processes AFTER_ACL_DELETE configuration settings -->
    <bean id="afterAclDelete" class="org.springside.modules.security.afterinvocation.DeleteAclEntryAfterInvocationProvider">
        <property name="aclDAO">
            <ref local="basicAclExtendedDao"/>
        </property>
    </bean>

    <!-- Processes AFTER_ACL_CREAT configuration settings -->
    <bean id="afterAclCreat" class="org.springside.modules.security.afterinvocation.CreatAclEntryAfterInvocationProvider">
        <property name="processDomainObjectClass">
            <value>org.springside.modules.security.acl.domain.AclDomainAware</value>
        </property>
        <property name="creators">
            <list>
                <ref local="droolsAclCreator"/>
            </list>
        </property>
    </bean>

    <!-- ACL_CREATORS configuration settings -->
    <bean id="droolsAclCreator" class="org.springside.modules.security.acl.creator.DroolsRuleAclCreator">
        <property name="aclDAO">
            <ref local="basicAclExtendedDao"/>
        </property>
        <property name="roleDao">
            <ref bean="roleDao"/>
        </property>
        <property name="userDao">
            <ref bean="userDao"/>
        </property>
        <property name="ruleTemplate">
            <ref bean="aclRuleTemplate"/>
        </property>
        <property name="aclRuleGroup" value="aclCreatRule"/>
    </bean>
    
    <!-- 判断acl权限的RuleTemplate -->
    <bean id="aclRuleTemplate" class="org.springside.modules.rule.support.RuleTemplateImpl">
        <property name="ruleBaseLoader">
        	<bean class="org.springside.modules.rule.support.DRLRuleBaseLoader">
        		<property name="ruleFiles">
        			<value>classpath*:rules/acl/**.drl</value>
        		</property>
			</bean>
        </property>
    </bean>

    <!-- ================= METHOD INVOCATION AUTHORIZATION ==================== -->
    <!-- methodSecurityInterceptor在执行方法前进行拦截，检查用户权限信息 -->
    <bean id="methodSecurityInterceptor" class="org.acegisecurity.intercept.method.aopalliance.MethodSecurityInterceptor">
        <property name="authenticationManager" ref="authenticationManager"/>
        <property name="accessDecisionManager" ref="businessAccessDecisionManager"/>
        <property name="afterInvocationManager" ref="afterInvocationManager"/>
        <property name="objectDefinitionSource" ref="methodDefinitionSource"/>
        <property name="validateConfigAttributes">
        	<value>false</value>
        </property>
    </bean>

    <!-- ================= 自定义MethodDefinitionSource从cache中读取权限 ==================== -->
    <bean id="methodDefinitionSource" class="org.springside.modules.security.service.acegi.DBMethodDefinitionSource">
        <property name="acegiCacheManager" ref="acegiCacheManager"/>
    </bean>

</beans>
